home *** CD-ROM | disk | FTP | other *** search
/ Visual Basic Source Code / Visual Basic Source Code.iso / vbsource / powervww / pvini.cpp < prev    next >
C/C++ Source or Header  |  1998-01-05  |  9KB  |  407 lines

  1. //  ____________________________________________________
  2. // |                                                    |
  3. // |  Project:     POWER VIEW INTERFACE                 |
  4. // |  File:        PVINI.CPP                            |
  5. // |  Compiler:    WPP386 (10.6)                        |
  6. // |                                                    |
  7. // |  Subject:     INI files processor implementation   |
  8. // |                                                    |
  9. // |  Author:      Emil Dotchevski                      |
  10. // |____________________________________________________|
  11. //
  12. // E-mail: zajo@geocities.com
  13. // URL:    http://www.geocities.com/SiliconValley/Bay/3577
  14.  
  15. #ifndef NOINI
  16.  
  17. #define uses_conio
  18. #define uses_ctype
  19. #define uses_errno
  20. #define uses_io
  21. #define uses_fcntl
  22. #define uses_stdarg
  23. #define uses_stdio
  24. #define uses_string
  25. #define uses_ini
  26. #define uses_system
  27.  
  28. #include "PVuses.h"
  29.  
  30. #define EC_BAD_INI 223
  31.  
  32. class Tini
  33. {
  34.   public:
  35.     boolean valid;
  36.     boolean report;
  37.     char *filename;
  38.     char buffer[256];
  39.     uint cur_line;
  40.     uint cur_section_ofs;
  41.     uint cur_section_line;
  42.     char *cur_section;
  43.     Tini( char *_filename );
  44.     virtual ~Tini( void );
  45.     virtual void seek( uint line, uint offset )=0;
  46.     virtual uint get_seed( void )=0;
  47.     virtual char *next_line( void )=0;
  48.     boolean seek_section( boolean fatal, char *section );
  49.     char *seek_var( boolean fatal, char *var );
  50. };
  51.  
  52. class Tini_ro : public Tini
  53. {
  54.   public:
  55.     FILE *ini_file;
  56.     Tini_ro( char *_filename );
  57.     virtual ~Tini_ro( void );
  58.     virtual void seek( uint line, uint offset );
  59.     virtual uint get_seed( void );
  60.     virtual char *next_line( void );
  61. };
  62.  
  63. class Tini_rw : public Tini, public Ttext_editor
  64. {
  65.   public:
  66.     uint cur_line_ptr;
  67.     Tini_rw( char *_filename );
  68.     virtual void seek( uint line, uint offset );
  69.     virtual uint get_seed( void );
  70.     virtual char *next_line( void );
  71. };
  72.  
  73. /*
  74. Tini
  75. */
  76.   Tini::Tini( char *_filename )
  77.   {
  78.     report = 1;
  79.     filename = STRDUP(min_path(fexpand(strcpy(buffer,_filename))));
  80.   }
  81.  
  82.   Tini::~Tini( void )
  83.   {
  84.     FREE( filename );
  85.   }
  86.  
  87.   boolean Tini::seek_section( boolean fatal, char *section )
  88.   {
  89.     uint i;
  90.     cur_section = NULL;
  91.     for( i=0; i<2; i++ )
  92.     {
  93.       while( next_line()!=NULL )
  94.         if( stricmp( buffer, section )==0 )
  95.         {
  96.           cur_section = section;
  97.           cur_section_ofs = get_seed();
  98.           cur_section_line = cur_line;
  99.           return 1;
  100.         }
  101.       seek( 0, 0 );
  102.       cur_section_line = cur_line;
  103.     }
  104. #ifdef CYR
  105.     ini_err( fatal, "▒Ѭ╢¿┐▓á %s ¡Ñ Ñ ¡á¼Ñ░Ñ¡á", section );
  106. #else
  107.     ini_err( fatal, "section %s not found", section );
  108. #endif
  109.     return 0;
  110.   }
  111.  
  112.   char *Tini::seek_var( boolean fatal, char *var )
  113.   {
  114.     uint i;
  115.     for( i=0; i<2; i++ )
  116.     {
  117.       while( next_line()!=NULL && *buffer!='[' )
  118.       {
  119.         char *n;
  120.         char *p = strchr( buffer, '=' );
  121. #ifdef CYR
  122.         ini_lnerr( p==NULL, "▒¿¡▓á¬▓¿╖¡á ú░Ñ╕¬á" );
  123. #else
  124.         ini_lnerr( p==NULL, "syntax error" );
  125. #endif
  126.         *p = 0; n = p;
  127.         while( *buffer && *--n==' ' ) *n = 0;
  128.         if( stricmp( var, buffer )==0 )
  129.         {
  130.           strcpy( buffer, p+1 );
  131.           return buffer;
  132.         }
  133.       }
  134.       seek( cur_section_line, cur_section_ofs );
  135.     }
  136. #ifdef CYR
  137.     ini_err( fatal, "»░«¼Ñ¡½¿óá▓á '%s' ¡Ñ Ñ ¡á¼Ñ░Ñ¡á, ▒Ѭ╢¿┐ %s", var, cur_section );
  138. #else
  139.     ini_err( fatal, "variable '%s' not found, section %s", var, cur_section );
  140. #endif
  141.     return NULL;
  142.   }
  143.  
  144.  
  145. /*
  146. Tini_ro
  147. */
  148.   Tini_ro::Tini_ro( char *_filename ):
  149.     Tini( _filename )
  150.   {
  151.     ini_file = fopen( filename, "rt" );
  152.     valid = ini_file!=NULL;
  153.     if( valid ) seek( 0, 0 );
  154.   }
  155.  
  156.   Tini_ro::~Tini_ro( void )
  157.   {
  158.     fclose( ini_file );
  159.   }
  160.  
  161.   void Tini_ro::seek( uint line, uint offset )
  162.   {
  163. #ifdef CYR
  164.     ini_err( fseek( ini_file, offset, SEEK_SET )!=0, "¡Ñ│▒»Ñ╕¡« »«º¿╢¿«¡¿░á¡Ñ" );
  165. #else
  166.     ini_err( fseek( ini_file, offset, SEEK_SET )!=0, "seek failed" );
  167. #endif
  168.     cur_line=line;
  169.   }
  170.  
  171.   uint Tini_ro::get_seed( void )
  172.   {
  173.     return ftell( ini_file );
  174.   }
  175.  
  176.   char *Tini_ro::next_line( void )
  177.   {
  178.     loop:
  179.       if( errno=0, fgets( buffer, sizeof(buffer), ini_file )!=NULL )
  180.       {
  181.         char *p = strchr( buffer, ';' );
  182.         cur_line++;
  183.         if( p != NULL ) *p = 0;                  //cut comments
  184.         p = strchr( buffer, '\n' );
  185.         if( p != NULL ) *p = 0;                  //cut eol
  186.         p = strchr( buffer, 0 );
  187.         while( p>buffer && *(--p)==' ' ) *p = 0; //cut eol spaces
  188.         if( *buffer==0 ) goto loop;
  189.         return strupr( buffer );
  190.       }
  191. #ifdef CYR
  192.     ini_err( errno!=EZERO, "ú░Ñ╕¬á »░¿ ╖Ñ▓Ñ¡Ñ ¡á ini ┤á⌐½á" );
  193. #else
  194.     ini_err( errno!=EZERO, "can't read ini file" );
  195. #endif
  196.     return NULL;
  197.   }
  198.  
  199.  
  200. /*
  201. Tini_rw
  202. */
  203.   Tini_rw::Tini_rw( char *_filename ):
  204.     Tini( _filename ),
  205.     Ttext_editor( 4096, NULL )
  206.   {
  207.     set_name( _filename );
  208.     valid = load();
  209.     if( valid ) seek( 0, 0 );
  210.   }
  211.  
  212.   #pragma off( unreferenced )
  213.   void Tini_rw::seek( uint line, uint offset )
  214.   {
  215.     set_cur_ptr( offset, 0 );
  216.     cur_line = cur_pos_y;
  217.   }
  218.   #pragma on( unreferenced )
  219.  
  220.   uint Tini_rw::get_seed( void )
  221.   {
  222.     return cur_ptr;
  223.   }
  224.  
  225.   char *Tini_rw::next_line( void )
  226.   {
  227.     loop:
  228.       if( cur_ptr>=buf_len ) return NULL;
  229.       get_line_str( buffer, sizeof(buffer) );
  230.       cur_line_ptr = cur_ptr;
  231.       set_cur_xy( 0, ++cur_line, 0 );
  232.       char *p = strchr( buffer, ';' );
  233.       if( p != NULL ) *p = 0;                  //cut comments
  234.       p = strchr( buffer, '\n' );
  235.       if( p != NULL ) *p = 0;                  //cut eol
  236.       p = strchr( buffer, 0 );
  237.       while( p>buffer && *(--p)==' ' ) *p = 0; //cut eol spaces
  238.       if( *buffer==0 ) goto loop;
  239.       return strupr( buffer );
  240.   }
  241.  
  242.  
  243. static Tini *cur_ini=NULL;
  244. #define INI_RO  ((Tini_ro *)cur_ini)
  245. #define INI_RW  ((Tini_rw *)cur_ini)
  246.  
  247. FILE *read_ini( char *filename )
  248. {
  249.   close_ini();
  250.   cur_ini = NEW( Tini_ro( filename ) );
  251.   if( !cur_ini->valid )
  252.   {
  253.     close_ini();
  254.     return NULL;
  255.   }
  256.   return INI_RO->ini_file;
  257. }
  258.  
  259. Ttext_editor *open_ini( char *filename )
  260. {
  261.   close_ini();
  262.   cur_ini = NEW( Tini_rw( filename ) );
  263.   if( !cur_ini->valid )
  264.   {
  265.     close_ini();
  266.     return NULL;
  267.   }
  268.   return (Ttext_editor *)INI_RW;
  269. }
  270.  
  271. void close_ini( void )
  272. {
  273.   if( cur_ini!=NULL ) DELETE( cur_ini );
  274.   cur_ini = NULL;
  275. }
  276.  
  277. boolean seek_section( boolean fatal, char *section )
  278. {
  279.   if( cur_ini==NULL ) return 0;
  280.   return cur_ini->seek_section( fatal, section );
  281. }
  282.  
  283. char *seek_var( boolean fatal, char *var )
  284. {
  285.   if( cur_ini==NULL ) return NULL;
  286.   return cur_ini->seek_var( fatal, var );
  287. }
  288.  
  289. boolean ini( char *var, boolean &x, boolean _default )
  290. {
  291.   long l;
  292.   x=_default;
  293.   if( !ini( var, l, (long)_default ) ) return 0;
  294. #ifdef CYR
  295.   ini_lnerr( l<0 || l>1, "Ä╖á¬óá ▒Ñ 0 ¿½¿ 1" );
  296. #else
  297.   ini_lnerr( l<0 || l>1, "0 or 1 expected" );
  298. #endif
  299.   x=l;
  300.   return 1;
  301. }
  302.  
  303. boolean ini( char *var, long &x, long _default )
  304. {
  305.   char *v;
  306.   x=_default;
  307.   if( cur_ini==NULL || cur_ini->cur_section==NULL || (v=seek_var(0,var))==NULL ) return 0;
  308. #ifdef CYR
  309.   ini_lnerr( sscanf(v,"%d",&x)!=1, "Ä╖á¬óá ▒Ñ ╢ѽ«╖¿▒½Ñ¡á ¬«¡▒▓á¡▓á" );
  310. #else
  311.   ini_lnerr( sscanf(v,"%d",&x)!=1, "Integer expected" );
  312. #endif
  313.   return 1;
  314. }
  315.  
  316. #ifndef NOFLOAT
  317. boolean ini( char *var, double &x, double _default )
  318. {
  319.   char *v;
  320.   x=_default;
  321.   if( cur_ini==NULL || cur_ini->cur_section==NULL || (v=seek_var(0,var))==NULL ) return 0;
  322. #ifdef CYR
  323.   ini_lnerr( sscanf(v,"%lf",&x)!=1, "Ä╖á¬óá ▒Ñ ñ░«í¡á ¬«¡▒▓á¡▓á" );
  324. #else
  325.   ini_lnerr( sscanf(v,"%lf",&x)!=1, "Floating point expected" );
  326. #endif
  327.   return 1;
  328. }
  329. #endif
  330.  
  331. boolean set_ini( char *var, char *value, ... )
  332. {
  333.   va_list argptr;
  334.   char buf[256];
  335.   if( seek_var( 0, var )==NULL ) return 0;
  336.   va_start( argptr, value );
  337.   vsprintf( buf, value, argptr );
  338.   va_end( argptr );
  339.   INI_RW->set_select( INI_RW->line_start(INI_RW->cur_line_ptr), INI_RW->line_end(INI_RW->cur_line_ptr), 0 );
  340.   INI_RW->insert_